#include "iotgo_platformAPI.h"
#include "iotgo_mySocketClient_interface.h"
#include "iotgo_config.h"
#include "iotgo_debug.h"
#include "iotgo_memory_hooks.h"


#if (POLARSSL_ON == 0 && GPRS_ON == 0)
#define MAX_DOMAIN_LEN 20
#define debugPrint socketClientDebugPrint

#define SOCKET_NOT_INITED            0
#define SOCKET_CONNECTION_IS_READY   1

#define SOCKET_PORT 8081 //this is for non-ssl port

struct mySocketClient_interface
{
    int32_t con_fd;
    struct sockaddr_in c_addr;
    volatile int8_t  state;
    uint8_t domain[MAX_DOMAIN_LEN];
    int32_t con_port;
    fd_set readfds;
};

MySocketClient *setupSocketClient(uint8_t *server_ip,uint32_t server_port)
{
    MySocketClient *p_socket = NULL;

    p_socket = (MySocketClient *) pMalloc(sizeof(MySocketClient));

    if(!p_socket)
    {
	debugPrint("[%s] p_socket without ssl is null\n",__FUNCTION__);
	return NULL;
    }

    memset(p_socket,0,sizeof(MySocketClient));
    p_socket->state = SOCKET_NOT_INITED;
    strcpy(p_socket->domain,server_ip);
    p_socket->con_port = server_port;
    return p_socket;
}


int8_t cleanSocketClient(MySocketClient **pp_mysocket)
{
	MySocketClient *p_mysocket = NULL;
	p_mysocket = *pp_mysocket;
    if(p_mysocket)
    {
        debugPrint("[%s] close the fd\n",__FUNCTION__);
        close(p_mysocket->con_fd);
        debugPrint("[%s] cleanSocketClient obj\n",__FUNCTION__);
	p_mysocket->state = SOCKET_NOT_INITED;
	pFree(p_mysocket);
    }
    return MYSOCKETCLIENT_SUCCESS;
}

int8_t connectToServer(MySocketClient *p_mysocket)
{
#if 0
    int8_t ret = -1;
    int32_t con_fd = -1;
    int8_t str[32];
    char **pptr;
	char *IP;
   
    struct hostent *host = NULL;

    if(p_mysocket)
    {
	debugPrint("[%s] parse the server domain name\n",__FUNCTION__);
	if( (host = gethostbyname(p_mysocket->domain)) == NULL)
	{
	    return MYSOCKETCLIENT_FAIL;
	}
	debugPrint("[%s] domain official name is %s\n",__FUNCTION__,host->h_name);

	pptr = host->h_aliases;
	for(; *pptr != NULL; pptr++)
	{
	    debugPrint("[%s] domain aliases  name is %s\n",__FUNCTION__,*pptr);
	}

	pptr = host->h_addr_list;
	inet_ntop(host->h_addrtype,*pptr,str,sizeof(str));
	IP = *pptr;
	for(; *pptr != NULL; pptr++)
	{
	    debugPrint("[%s] IP is %s\n",__FUNCTION__,inet_ntop(host->h_addrtype,*pptr,str,sizeof(str)));
	}

        debugPrint("[%s] start connect...\n",__FUNCTION__);
        p_mysocket->con_fd = socket(PF_INET,SOCK_STREAM,IPPROTO_TCP);
        memset(&(p_mysocket->c_addr),0,sizeof(struct sockaddr_in));
	p_mysocket->c_addr.sin_family = AF_INET;
	//p_mysocket->c_addr.sin_port = htons(p_mysocket->con_port);
	p_mysocket->c_addr.sin_port = htons(SOCKET_PORT);
	p_mysocket->c_addr.sin_addr.s_addr = inet_addr(IP);
	//inet_pton(host->h_addrtype,host->h_addr_list[0],&(p_mysocket->c_addr.sin_addr));
	  
	ret = connect(p_mysocket->con_fd,
		      (struct sockaddr *)&(p_mysocket->c_addr),
		      sizeof(struct sockaddr));

	if(ret < 0)
	{
	    debugPrint("[%s] make connect fd fail\n",__FUNCTION__);
	    debugPrint("[%s] server_ip is %s\n",__FUNCTION__,p_mysocket->domain);
	    debugPrint("[%s] server_ip is %d\n",__FUNCTION__,p_mysocket->con_port);
	    close(p_mysocket->con_fd);
	    return MYSOCKETCLIENT_FAIL;
	}
	debugPrint("[%s] socket connect done\n",__FUNCTION__);
	p_mysocket->state = SOCKET_CONNECTION_IS_READY;
	return MYSOCKETCLIENT_SUCCESS;
    }
#endif
    return MYSOCKETCLIENT_FAIL;
}


int32_t readFromServer(MySocketClient *p_mysocket,uint8_t *buf, uint32_t len)
{
    int32_t ret = -1;
    struct timeval timeout;
    timeout.tv_sec = 10000;
    timeout.tv_usec = 0;
    if(p_mysocket->state == SOCKET_CONNECTION_IS_READY)
    {
        FD_ZERO(&(p_mysocket->readfds));
        FD_SET(p_mysocket->con_fd,&(p_mysocket->readfds));
        ret = select(FD_SETSIZE, &(p_mysocket->readfds),NULL,NULL,&timeout);
        if(ret < 0)
        {
        
        }
        else if(ret == 0)
        {
        
        }
        else
        {
            ret = read(p_mysocket->con_fd,buf,len);
	    debugPrint("[%s]read ret is %d\n",__FUNCTION__,ret);
	    debugPrint("[%s]read is \n%s\n",__FUNCTION__,buf);
        }
    }
    return ret;

}

int32_t readFromServerNonBlock(MySocketClient *p_mysocket,uint8_t *buf, uint32_t len)
{
    int32_t ret;
    ret = readFromServer(p_mysocket,buf, len);
    return ret;
}


int32_t writeToServer(MySocketClient *p_mysocket,uint8_t *buf, uint32_t len)
{
    int32_t ret = -1;
    if(p_mysocket->state == SOCKET_CONNECTION_IS_READY)
    {
	//debugPrint("[%s] write buf is\n%s\n",__FUNCTION__,buf);
	ret = write(p_mysocket->con_fd,buf,len);
    }
    return ret;
}

#endif
